/*
 * Copyright 2011 Biz-e (info@biz-e.nl)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package nl.biz_e.android.calllog;

import java.util.Vector;

import nl.biz_e.android.calllog.dao.BussinessLogic;
import nl.biz_e.android.calllog.model.CallLogItem;
import nl.biz_e.android.calllog.util.CallLogPrefs;
import android.content.Context;
import android.graphics.Bitmap;
import android.text.format.DateFormat;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnLongClickListener;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.QuickContactBadge;
import android.widget.TextView;
import android.widget.Toast;

/**
 * Displays one instance of a {@link CallLogItem} in the list.
 * 
 * @author Joost A. Bloemsma
 */
public class CallLogItemView extends LinearLayout implements OnClickListener, OnLongClickListener {
	private QuickContactBadge qcbContact;
	private TextView lblName;
	private TextView lblTime;
	private TextView lblType;
	private TextView lblNumber;
	private ImageView imgInfo;
	private Button btn;
	private CallLogItem item;
	private Vector<OnCallLogItemClickListener> clickListeners = new Vector<CallLogItemView.OnCallLogItemClickListener>();
	private Vector<OnCallLogItemLongClickListener> longClickListeners = new Vector<CallLogItemView.OnCallLogItemLongClickListener>();
	
	/**
	 * Enumerated events that can be triggered by user actions, and will be delegated to
	 * registered {@link OnCallLogItemClickListener}s and {@link OnCallLogItemLongClickListener}s.
	 *
	 */
	public enum Event {
		/** Message to store the item in the calendar as an event */
		EVENT_STORECAL,
		/** Message to store the item in the internal call log database */
		EVENT_STOREDB,
		/** NULL event... do nothing */
		EVENT_NULL
	}
	
	/**
	 * Constructs a new CallLogItemView instance
	 * @param context
	 */
	public CallLogItemView(Context context) {
		this(context,null);
	}

	/**
	 * Constructs a new CallLogItemView instance
	 * @param context
	 * @param item
	 */
	public CallLogItemView(Context context, CallLogItem item) {
		super(context);
		this.item = item;
		create();
		getComponents();
		btn.setOnClickListener(this);
		this.setCallLogItem(this.item);
	}
	
	/**
	 * Registers a {@link CallLogItem} instance on this view, and displays its properties
	 * @param item
	 */
	public void setCallLogItem(CallLogItem item) {
		if (this.item == null) return;
		this.item = item;
		String name = item.getCachedName();
		String number = item.getNumber();
		if (name == null) {
			name = CallLogApp.getAppContext().getString(R.string.unknown);
		}
		lblName.setText(name);
		lblTime.setText(DateFormat.format("dd-MM-yy, k:mm:ss", item.getDate()));
		lblType.setText(CallLogPrefs.getNumberTypeName(item.getCachedNumberType()));
		lblNumber.setText(number);
		Bitmap thumb = item.getThumb();
		if (thumb != null) {
			qcbContact.setImageBitmap(thumb);
		} else {
			qcbContact.setImageToDefault();
		}
		qcbContact.assignContactFromPhone(number, true);
		if (BussinessLogic.isLoggedItem(item)) {
			imgInfo.setVisibility(VISIBLE);
		} else {
			imgInfo.setVisibility(INVISIBLE);
		}
		
	}
	
	private void getComponents() {
		qcbContact = (QuickContactBadge)findViewById(R.id.qcbContact); 
		lblName = (TextView)findViewById(R.id.lblName);
		lblNumber = (TextView)findViewById(R.id.lblNumber);
		lblTime = (TextView)findViewById(R.id.lblTime);
		lblType = (TextView)findViewById(R.id.lblType);
		imgInfo = (ImageView)findViewById(R.id.imgInfo);
		btn = (Button)findViewById(R.id.btn);
	}
	
	private void create() {
		LayoutInflater layoutInflater = (LayoutInflater)CallLogApp.getAppContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
		layoutInflater.inflate(R.layout.callitem, this, true);
	}
	
	/**
	 * Returns a reference to the registered {@link CallLogItem} instance
	 * @return the {@link CallLogItem} instance
	 */
	public CallLogItem getItem() {
		return this.item;
	}
	
	/**
	 * Adds an implementation of {@link OnCallLogItemClickListener} to the queue to be
	 * triggered when the event occurs. 
	 * @param listener An implementation of {@link OnCallLogItemClickListener} 
	 */
	public void addOnCallLogItemClickListener(OnCallLogItemClickListener listener) {
		if (!clickListeners.contains(listener)) clickListeners.add(listener);
	}
	
	/**
	 * Removes an implementation of {@link OnCallLogItemClickListener} from the queue
	 * @param listener An implementation of {@link OnCallLogItemClickListener} 
	 */
	public void removeOnCallLogItemClickListener(OnCallLogItemClickListener listener) {
		clickListeners.remove(listener);
	}
	
	/**
	 * Adds an implementation of {@link OnCallLogItemLongClickListener} to the queue to be
	 * triggered when the event occurs. 
	 * @param listener An implementation of {@link OnCallLogItemLongClickListener} 
	 */
	public void addOnCallLogItemLongClickListener(OnCallLogItemLongClickListener listener) {
		if (!longClickListeners.contains(listener)) longClickListeners.add(listener);
	}
	
	/**
	 * Removes an implementation of {@link OnCallLogItemLongClickListener} from the queue
	 * @param listener An implementation of {@link OnCallLogItemLongClickListener} 
	 */
	public void removeOnCallLogItemLongClickListener(OnCallLogItemLongClickListener listener) {
		longClickListeners.remove(listener);
	}
	
	/**
	 * {@inheritDoc}
	 */
	public void onClick(View v) {
		Event event = Event.EVENT_NULL ;
		if (v == btn) event = Event.EVENT_STORECAL;
		for (OnCallLogItemClickListener listener : clickListeners) {
			if (listener != null) listener.onCallLogItemClicked(this, event);
		}
	}
	
	/**
	 * {@inheritDoc}
	 */
	public boolean onLongClick(View v) {
		boolean consumed = false;
		Event event = Event.EVENT_NULL ;
		if (v == btn) event = Event.EVENT_STORECAL;
		
		for (OnCallLogItemLongClickListener listener : longClickListeners) {
			if (listener != null) {
				if (listener.onCallLogItemLongClicked(this, event)) consumed = true;
			}
		}
		Toast.makeText(getContext(), "LongClicked", Toast.LENGTH_SHORT);
		return consumed;
	}

	/**
	 * Defines the callback method to be triggered when an OnClick event occurs.
	 */
	public static interface OnCallLogItemClickListener {
		
		/**
		 * Will be triggered when an onClick event occurs
		 * @param view The {@link CallLogItemView} that triggered the event
		 * @param event One of the {@link Event} enumerations
		 */
		public void onCallLogItemClicked(CallLogItemView view, Event event);
	}
	
	/**
	 * Defines the callback method to be triggered when an OnLongClick event occurs.
	 */
	public static interface OnCallLogItemLongClickListener {
		
		/**
		 * Will be triggered when an onLongClick event occurs
		 * @param view The {@link CallLogItemView} that triggered the event
		 * @param event One of the {@link Event} enumerations
		 * @return True if the event is consumed, and should not be delegated any further
		 */
		public boolean onCallLogItemLongClicked(CallLogItemView view, Event event);
	}
}

